package com.betterjr.modules.application.service;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.betterjr.common.service.BaseService;
import com.betterjr.common.utils.BTAssert;
import com.betterjr.common.utils.CacheUtils;
import com.betterjr.common.utils.Collections3;
import com.betterjr.common.utils.QueryTermBuilder;
import com.betterjr.common.utils.UserUtils;
import com.betterjr.modules.application.dao.ApplicationGroupMapper;
import com.betterjr.modules.application.data.ApplicationConstantCollections;
import com.betterjr.modules.application.data.ApplicationGroupConstantCollections;
import com.betterjr.modules.application.data.ApplicationOperorgConstantCollections;
import com.betterjr.modules.application.entity.Application;
import com.betterjr.modules.application.entity.ApplicationGroup;
import com.betterjr.modules.customer.service.CustMajorService;

/**
 * 
 * @ClassName: ApplicationGroupService 
 * @Description: 应用分组服务 
 * @author xuyp
 * @date 2017年11月17日 下午6:05:50 
 *
 */
@Service
public class ApplicationGroupService extends BaseService<ApplicationGroupMapper, ApplicationGroup> {

    @Autowired
    private ApplicationService applicationService;

    @Autowired
    private ApplicationOperorgService operorgService;

    @Autowired
    private CustMajorService custMajorService;

    @Autowired
    private ApplicationCustRoleService applicationCustRoleService;

    /**
     * 
     * @Title: saveOrUpdateApplicationGroup 
     * @Description: 新增或者修改应用分组 
     * @param anApplicationGroup
     * @return 新增或者修改应用分组 
     * @throws 
     * @author xuyp
     * @date 2017年11月15日 下午3:00:04
     */
    public ApplicationGroup saveOrUpdateApplicationGroup(ApplicationGroup anApplicationGroup) {

        BTAssert.notNull(anApplicationGroup, "数据为空,操作失败");

        if (StringUtils.isBlank(anApplicationGroup.getApplicationGroupName())) {
            BTAssert.notNull(null, "数据为空,操作失败");
        }

        if (null == anApplicationGroup.getId()) {
            // add
            anApplicationGroup.saveModifyValue(UserUtils.getOperatorInfo(), "1");
            this.insertSelective(anApplicationGroup);
        } else {
            // modify
            ApplicationGroup applicationGroup = this.selectByPrimaryKey(anApplicationGroup.getId());
            BTAssert.notNull(applicationGroup, "数据为空,操作失败");
            BTAssert.isTrue(
                    !applicationGroup.getBusinStatus()
                            .equals(ApplicationGroupConstantCollections.APPLICATIONGROUP_BUSINSTATUS_DELETED),
                    "当前分组已经删除,操作失败");
            anApplicationGroup.saveModifyValue(UserUtils.getOperatorInfo(), "2");
            anApplicationGroup.setBusinStatus(applicationGroup.getBusinStatus());
            this.updateByPrimaryKeySelective(anApplicationGroup);
        }

        return anApplicationGroup;
    }

    /**
     * 
     * @Title: saveDeleteApplicationGroup 
     * @Description: 删除应用分组 
     * @param anGroupId
     * @return 删除应用分组
     * @throws 
     * @author xuyp
     * @date 2017年12月5日 下午4:40:42
     */
    public ApplicationGroup saveDeleteApplicationGroup(Long anGroupId) {

        BTAssert.isTrue(UserUtils.platformUser(), "你没有删除权限");

        BTAssert.notNull(anGroupId, "数据为空,操作失败");
        ApplicationGroup group = this.selectByPrimaryKey(anGroupId);
        BTAssert.notNull(group, "数据为空,操作失败");
        BTAssert.isTrue(!ApplicationGroupConstantCollections.APPLICATIONGROUP_BUSINSTATUS_DELETED
                .equals(group.getBusinStatus()), "当前分组已经删除");

        List<Application> applications = applicationService.queryEffectiveApplicationsByApplicationType(null, anGroupId,
                ApplicationOperorgConstantCollections.APPLICATIONOPERORG_BUSINSTATUS_CANUSED);
        BTAssert.isTrue(Collections3.isEmpty(applications), "当前分组已经有应用信息!操作失败");

        group.setBusinStatus(ApplicationGroupConstantCollections.APPLICATIONGROUP_BUSINSTATUS_DELETED);
        this.updateByPrimaryKeySelective(group);
        return group;

    }

    /**
     * 
     * @Title: findApplicationGroupDetail 
     * @Description: 查询单条分组应用的详细信息
     * @param anGroupId
     * @param anCount 是否查询应用数量 1 查询     2 不查询
     * @param anApplicaitonList   是否查询应用集合  1 查询  2 不查询
     * @param anBusinStatus   应用机构的状态状态 1未生效 2已生效 9已失效
     * @return 查询单条分组应用的详细信息
     * @throws 
     * @author xuyp
     * @date 2017年11月15日 下午3:50:52
     */
    public ApplicationGroup findApplicationGroupDetail(Long anGroupId, String anCount, String anApplicaitonList,
            String anBusinStatus) {

        BTAssert.notNull(anGroupId, "查询条件为空,操作失败");
        ApplicationGroup group = this.selectByPrimaryKey(anGroupId);
        BTAssert.notNull(group, "查询条件为空,操作失败");
        List<Application> applicationList = new ArrayList<>();
        if ("1".equals(anCount)) {
            applicationList = queryApplications(anGroupId, anBusinStatus);
            group.setAppliationCount(applicationList.size());
        }

        if ("1".equals(anApplicaitonList)) {
            if (Collections3.isEmpty(applicationList)) {
                applicationList = queryApplications(anGroupId, anBusinStatus);
            }
            group.setApplicationList(applicationList);
        }

        return group;

    }

    /**
     * 
     * @Title: queryApplications 
     * @Description: 根据当前登录的角色查询当前角色在当前应用分组下的所有应用信息
     * @param anGroupId
     * @param anBusinStatus   状态 1未生效 2已生效 9已失效
     * @return 根据当前登录的角色查询当前角色在当前应用分组下的所有应用信息
     * @throws 
     * @author xuyp
     * @date 2017年11月21日 下午3:25:13
     */
    public List<Application> queryApplications(Long anGroupId, String anBusinStatus) {
        // System.out.println(UserUtils.findRuleList());
        // System.out.println(UserUtils.findInnerRules());
        // System.out.println(UserUtils.getUserRole());
        // 得到角色名称 (管理员是：OPERATOR_ADMIN)
        String ruleList = UserUtils.getOperatorInfo().getRuleList();
        // System.out.println(ruleList);
        // 得到平台操作机构
        String operOrg = custMajorService.findPlatCustMajorDetail().getOperOrg();
        // 如果是管理员并且是平台 查询所有的应用
        if (ApplicationConstantCollections.APPLICATION_OPERATOR_ADMIN.equals(ruleList)
                && UserUtils.getOperatorInfo().getOperOrg().equals(operOrg)) {
            return applicationService.queryEffectiveApplicationsByApplicationType(null, anGroupId, anBusinStatus);
        }

        // 如果是管理员 从应用机构表中查询数量
        if (ApplicationConstantCollections.APPLICATION_OPERATOR_ADMIN.equals(ruleList)) {

            return operorgService.queryApplication(null, anGroupId, anBusinStatus);
        }

        // 最后从应用公司角色表中获取数量

        return applicationCustRoleService.queryApplicationsCurrentUser(null, anGroupId, anBusinStatus);

    }

    private boolean checkOperatorIsPlatformAdmin() {

        String operOrg = custMajorService.findPlatCustMajorDetail().getOperOrg();
        String ruleList = UserUtils.getOperatorInfo().getRuleList();

        // 如果是管理员并且是平台 查询所有的应用
        if (ApplicationConstantCollections.APPLICATION_OPERATOR_ADMIN.equals(ruleList)
                && UserUtils.getOperatorInfo().getOperOrg().equals(operOrg)) {
            return true;
        }

        return false;
    }

    /**
     * 
     * @Title: queryApplicationGroupList 
     * @Description: 根据分组查询所有的应用 
     * @param anCount 是否查询应用数量 1 查询     2 不查询
     * @param anApplicaitonList   是否查询应用集合  1 查询  2 不查询
     * @param anBusinStatus   状态应用中间表中的状态状态 1未生效 2已生效 9已失效
     * @return 根据分组查询所有的应用 
     * @throws 
     * @author xuyp
     * @date 2017年11月15日 下午4:10:00
     */
    @SuppressWarnings("unchecked")
    public List<ApplicationGroup> queryApplicationGroupList(String anCount, String anApplicaitonList,
            String anBusinStatus) {

        Map<String, Object> map = QueryTermBuilder.newInstance()
                .put("businStatus", ApplicationGroupConstantCollections.APPLICATIONGROUP_BUSINSTATUS_OK).build();
        List<ApplicationGroup> list = this.selectByProperty(map, "id Desc");
        List<ApplicationGroup> groupList = new ArrayList<>(list.size());
        // 设置默认状态
        if (StringUtils.isBlank(anBusinStatus)) {
            anBusinStatus = ApplicationOperorgConstantCollections.APPLICATIONOPERORG_BUSINSTATUS_EFFECTIVE;
        }
        for (ApplicationGroup applicationGroup : list) {
            ApplicationGroup group = findApplicationGroupDetail(applicationGroup.getId(), anCount, anApplicaitonList,
                    anBusinStatus);
            if (group != null && !Collections3.isEmpty(group.getApplicationList())) {

                groupList.add(group);
            } else {
                // 如果是平台管理员查询出空分组
                if (checkOperatorIsPlatformAdmin()) {
                    groupList.add(group);
                }
            }

        }

        return groupList;
    }

    /**
     * 
     * @Title: findApplicationGroupNameById 
     * @Description: 查询应用分组的名称
     * @param anApplicationGroupId 应用分组id
     * @return 查询应用分组的名称
     * @throws 
     * @author xuyp
     * @date 2017年11月16日 下午1:49:02
     */
    public String findApplicationGroupNameById(Long anApplicationGroupId) {

        String applicationName = "";
        try {
            Object object = CacheUtils
                    .get(ApplicationGroupConstantCollections.APPLIATIONGROUP_REDIS_APPLICAITONGROUPNAME_KEY
                            + anApplicationGroupId);
            if (object != null) {
                applicationName = object.toString();
            }
        }
        catch (Exception e) {
            logger.info("redis exception" + e.getMessage());
        }

        if (StringUtils.isBlank(applicationName)) {
            ApplicationGroup applicationGroup = this.selectByPrimaryKey(anApplicationGroupId);

            applicationName = applicationGroup.getApplicationGroupName();
            try {
                CacheUtils.put(ApplicationGroupConstantCollections.APPLIATIONGROUP_REDIS_APPLICAITONGROUPNAME_KEY
                        + anApplicationGroupId, applicationName);
            }
            catch (Exception e) {
                logger.info("redis exception" + e.getMessage());
            }
        }

        return applicationName;

    }

}
